home *** CD-ROM | disk | FTP | other *** search
- Path: uunet!seismo!columbia!rutgers!sri-spam!ames!ucbcad!zen!ucbvax!decvax!tektronix!tekgen!tekred!games-request
- From: games-request@tekred.TEK.COM
- Newsgroups: comp.sources.games
- Subject: v02i007: nethack - display oriented dungeons & dragons, Part07/16
- Message-ID: <1449@tekred.TEK.COM>
- Date: 28 Jul 87 17:49:12 GMT
- Sender: billr@tekred.TEK.COM
- Lines: 2471
- Approved: billr@tekred.TEK.COM
-
- Submitted by: mike@genat.UUCP (Mike Stephenson)
- Comp.sources.games: Volume 2, Issue 7
- Archive-name: nethack/Part07
-
-
-
- #! /bin/sh
- # This is a shell archive. Remove anything before this line, then unpack
- # it by saving it into a file and typing "sh file". To overwrite existing
- # files, type "sh file -c". You can also feed this as standard input via
- # unshar, or by typing "sh <file", e.g.. If this archive is complete, you
- # will see the following message at the end:
- # "End of archive 7 (of 16)."
- # Contents: msdos.c objnam.c potion.c unixunix.c
- # Wrapped by billr@tekred on Tue Jul 28 09:49:32 1987
- PATH=/bin:/usr/bin:/usr/ucb ; export PATH
- if test -f msdos.c -a "${1}" != "-c" ; then
- echo shar: Will not over-write existing file \"msdos.c\"
- else
- echo shar: Extracting \"msdos.c\" \(13705 characters\)
- sed "s/^X//" >msdos.c <<'END_OF_msdos.c'
- X/* SCCS Id: @(#)msdos.c 1.3 87/07/14
- X/* An assortment of MSDOS functions.
- X */
- X
- X#include <stdio.h>
- X#include "hack.h"
- X
- X#ifdef MSDOS
- X# include <dos.h>
- X
- Xvoid
- Xflushout()
- X{
- X (void) fflush(stdout);
- X}
- X
- Xgetuid() {
- X return 1;
- X}
- X
- Xchar *
- Xgetlogin() {
- X return ((char *) NULL);
- X}
- X
- Xtgetch() {
- X char ch, popch();
- X static char DOSgetch(), BIOSgetch();
- X
- X if (!(ch = popch())) {
- X# ifdef DGK
- X /* BIOSgetch can use the numeric key pad on IBM compatibles. */
- X if (flags.IBMBIOS)
- X ch = BIOSgetch();
- X else
- X# endif
- X ch = DOSgetch();
- X }
- X return ((ch == '\r') ? '\n' : ch);
- X}
- X
- X# define DIRECT_INPUT 0x7
- Xstatic char
- XDOSgetch() {
- X union REGS regs;
- X
- X regs.h.ah = DIRECT_INPUT;
- X intdos(®s, ®s);
- X if (!regs.h.al) { /* an extended code -- not yet supported */
- X regs.h.ah = DIRECT_INPUT;
- X intdos(®s, ®s); /* eat the next character */
- X regs.h.al = 0; /* and return a 0 */
- X }
- X return (regs.h.al);
- X}
- X
- X
- X# ifdef DGK
- X# include <ctype.h>
- X# include <fcntl.h>
- X
- X# define Sprintf (void) sprintf
- X# define WARN 1
- X# define NOWARN 0
- X
- Xstatic char *
- Xgetcomspec(warn) {
- X return getenv("COMSPEC");
- X}
- X
- X# ifdef SHELL
- X# include <process.h>
- Xdosh() {
- X extern char orgdir[];
- X char *comspec;
- X
- X if (comspec = getcomspec()) {
- X settty("To return to HACK, type \"exit\" at the DOS prompt.\n");
- X chdirx(orgdir, 0);
- X if (spawnl(P_WAIT, comspec, comspec, NULL) < 0) {
- X printf("\nCan't spawn %s !\n", comspec);
- X flags.toplin = 0;
- X more();
- X }
- X chdirx(hackdir, 0);
- X start_screen();
- X docrt();
- X } else
- X pline("No COMSPEC !? Can't exec COMMAND.COM");
- X return(0);
- X}
- X# endif /* SHELL */
- X
- X/* Normal characters are output when the shift key is not pushed.
- X * Shift characters are output when either shift key is pushed.
- X */
- X# define KEYPADHI 83
- X# define KEYPADLOW 71
- X# define iskeypad(x) (KEYPADLOW <= (x) && (x) <= KEYPADHI)
- Xstatic struct {
- X char normal, shift;
- X } keypad[KEYPADHI - KEYPADLOW + 1] = {
- X {'y', 'Y'}, /* 7 */
- X {'k', 'K'}, /* 8 */
- X {'u', 'U'}, /* 9 */
- X {'m', CTRL('P')}, /* - */
- X {'h', 'H'}, /* 4 */
- X {'g', 'g'}, /* 5 */
- X {'l', 'L'}, /* 6 */
- X {'p', 'P'}, /* + */
- X {'b', 'B'}, /* 1 */
- X {'j', 'J'}, /* 2 */
- X {'n', 'N'}, /* 3 */
- X {'i', 'I'}, /* Ins */
- X {'.', ':'} /* Del */
- X};
- X
- X/* BIOSgetch gets keys directly with a BIOS call.
- X */
- X# define SHIFT (0x1 | 0x2)
- X# define KEYBRD_BIOS 0x16
- X
- Xstatic char
- XBIOSgetch() {
- X unsigned char scan, shift, ch;
- X union REGS regs;
- X
- X /* Get scan code.
- X */
- X regs.h.ah = 0;
- X int86(KEYBRD_BIOS, ®s, ®s);
- X ch = regs.h.al;
- X scan = regs.h.ah;
- X
- X /* Get shift status.
- X */
- X regs.h.ah = 2;
- X int86(KEYBRD_BIOS, ®s, ®s);
- X shift = regs.h.al;
- X
- X /* If scan code is for the keypad, translate it.
- X */
- X if (iskeypad(scan)) {
- X if (shift & SHIFT)
- X ch = keypad[scan - KEYPADLOW].shift;
- X else
- X ch = keypad[scan - KEYPADLOW].normal;
- X }
- X return ch;
- X}
- X
- X/* construct the string file.level */
- Xvoid
- Xname_file(file, level)
- Xchar *file;
- Xint level;
- X{
- X char *tf;
- X
- X if (tf = rindex(file, '.'))
- X Sprintf(tf+1, "%d", level);
- X}
- X
- X
- X# define FINDFIRST 0x4E00
- X# define FINDNEXT 0x4F00
- X# define GETDTA 0x2F00
- X# define SETFILETIME 0x5701
- X# define GETSWITCHAR 0x3700
- X# define FREESPACE 0x36
- X
- Xstatic char
- Xswitchar()
- X{
- X union REGS regs;
- X
- X regs.x.ax = GETSWITCHAR;
- X intdos(®s, ®s);
- X return regs.h.dl;
- X}
- X
- Xlong
- Xfreediskspace(path)
- Xchar *path;
- X{
- X union REGS regs;
- X
- X regs.h.ah = FREESPACE;
- X if (path[0] && path[1] == ':')
- X regs.h.dl = (toupper(path[0]) - 'A') + 1;
- X else
- X regs.h.dl = 0;
- X intdos(®s, ®s);
- X if (regs.x.ax == 0xFFFF)
- X return -1L; /* bad drive number */
- X else
- X return ((long) regs.x.bx * regs.x.cx * regs.x.ax);
- X}
- X
- X/* Functions to get filenames using wildcards
- X */
- Xstatic
- Xfindfirst(path)
- Xchar *path;
- X{
- X union REGS regs;
- X struct SREGS sregs;
- X
- X regs.x.ax = FINDFIRST;
- X regs.x.cx = 0; /* normal files */
- X regs.x.dx = FP_OFF(path);
- X sregs.ds = FP_SEG(path);
- X intdosx(®s, ®s, &sregs);
- X return !regs.x.cflag;
- X}
- X
- Xstatic
- Xfindnext() {
- X union REGS regs;
- X
- X regs.x.ax = FINDNEXT;
- X intdos(®s, ®s);
- X return !regs.x.cflag;
- X}
- X
- X/* Get disk transfer area */
- Xstatic char *
- Xgetdta() {
- X union REGS regs;
- X struct SREGS sregs;
- X char *ret;
- X
- X regs.x.ax = GETDTA;
- X intdosx(®s, ®s, &sregs);
- X FP_OFF(ret) = regs.x.bx;
- X FP_SEG(ret) = sregs.es;
- X return ret;
- X}
- X
- Xlong
- Xfilesize(file)
- Xchar *file;
- X{
- X char *dta;
- X
- X if (findfirst(file)) {
- X dta = getdta();
- X return (* (long *) (dta + 26));
- X } else
- X return -1L;
- X}
- X
- Xvoid
- Xeraseall(path, files)
- Xchar *path, *files;
- X{
- X char *getdta(), *dta, buf[PATHLEN];
- X
- X dta = getdta();
- X Sprintf(buf, "%s%s", path, files);
- X if (findfirst(buf))
- X do {
- X Sprintf(buf, "%s%s", path, dta + 30);
- X (void) unlink(buf);
- X } while (findnext());
- X}
- X
- X/* Rewritten for version 3.3 to be faster
- X */
- Xvoid
- Xcopybones(mode) {
- X char from[PATHLEN], to[PATHLEN], last[13], copy[8];
- X char *frompath, *topath, *dta, *comspec;
- X int status;
- X long fs;
- X extern saveprompt;
- X
- X if (!ramdisk)
- X return;
- X
- X /* Find the name of the last file to be transferred
- X */
- X frompath = (mode != TOPERM) ? permbones : levels;
- X dta = getdta();
- X last[0] = '\0';
- X Sprintf(from, "%s%s", frompath, allbones);
- X if (findfirst(from))
- X do {
- X strcpy(last, dta + 30);
- X } while (findnext());
- X
- X topath = (mode == TOPERM) ? permbones : levels;
- X if (last[0]) {
- X Sprintf(copy, "%cC copy", switchar());
- X
- X /* Remove any bones files in `to' directory.
- X */
- X eraseall(topath, allbones);
- X
- X /* Copy `from' to `to' */
- X Sprintf(to, "%s%s", topath, allbones);
- X comspec = getcomspec();
- X status =spawnl(P_WAIT, comspec, comspec, copy, from,
- X to, "> nul", NULL);
- X } else
- X return;
- X
- X /* See if the last file got there. If so, remove the ramdisk bones
- X * files.
- X */
- X Sprintf(to, "%s%s", topath, last);
- X if (findfirst(to)) {
- X if (mode == TOPERM)
- X eraseall(frompath, allbones);
- X return;
- X }
- X
- X /* Last file didn't get there.
- X */
- X Sprintf(to, "%s%s", topath, allbones);
- X msmsg("Cannot copy `%s' to `%s' -- %s\n", from, to,
- X (status < 0) ? "can't spawn COMSPEC !" :
- X (freediskspace(topath) < filesize(from)) ?
- X "insufficient disk space." : "bad path(s)?");
- X if (mode == TOPERM) {
- X msmsg("Bones will be left in `%s'\n",
- X *levels ? levels : hackdir);
- X return;
- X } else {
- X /* Remove all bones files on the RAMdisk */
- X eraseall(levels, allbones);
- X playwoRAMdisk();
- X }
- X}
- X
- XplaywoRAMdisk() {
- X msmsg("Do you wish to play without a RAMdisk (y/n) ? ");
- X
- X /* Set ramdisk false *before* exit'ing (because msexit calls
- X * copybones)
- X */
- X ramdisk = FALSE;
- X if (getchar() != 'y') {
- X settty("Be seeing you ...\n");
- X exit(0);
- X }
- X set_lock_and_bones();
- X return;
- X}
- X
- XsaveDiskPrompt(start) {
- X extern saveprompt;
- X char buf[BUFSIZ], *bp;
- X int fd;
- X
- X if (saveprompt) {
- X /* Don't prompt if you can find the save file */
- X if ((fd = open(SAVEF, 0)) >= 0) {
- X (void) close(fd);
- X return 1;
- X }
- X remember_topl();
- X home();
- X cl_end();
- X msmsg("If save file is on a SAVE disk, put that disk in now.\n");
- X cl_end();
- X msmsg("File name (default `%s'%s) ? ", SAVEF,
- X start ? "" : ", <Esc> cancels save");
- X getlin(buf);
- X home();
- X cl_end();
- X curs(1, 2);
- X cl_end();
- X if (!start && *buf == '\033')
- X return 0;
- X
- X /* Strip any whitespace. Also, if nothing was entered except
- X * whitespace, do not change the value of SAVEF.
- X */
- X for (bp = buf; *bp; bp++)
- X if (!isspace(*bp)) {
- X strncpy(SAVEF, bp, PATHLEN);
- X break;
- X }
- X }
- X return 1;
- X}
- X
- X/* Return 1 if the record file was found */
- Xstatic
- Xrecord_exists() {
- X int fd;
- X
- X if ((fd = open(RECORD, 0)) >= 0) {
- X close(fd);
- X return TRUE;
- X }
- X return FALSE;
- X}
- X
- X/* Return 1 if the comspec was found */
- Xstatic
- Xcomspec_exists() {
- X int fd;
- X char *comspec;
- X
- X if (comspec = getcomspec())
- X if ((fd = open(comspec, 0)) >= 0) {
- X close(fd);
- X return TRUE;
- X }
- X return FALSE;
- X}
- X
- X/* Prompt for game disk, then check for record file.
- X */
- Xvoid
- XgameDiskPrompt() {
- X extern saveprompt;
- X
- X if (saveprompt) {
- X if (record_exists() && comspec_exists())
- X return;
- X (void) putchar('\n');
- X getreturn("when the GAME disk has been put in");
- X }
- X if (comspec_exists() && record_exists())
- X return;
- X
- X if (!comspec_exists())
- X msmsg("\n\nWARNING: can't find comspec `%s'!\n", getcomspec());
- X if (!record_exists())
- X msmsg("\n\nWARNING: can't find record file `%s'!\n", RECORD);
- X msmsg("If the GAME disk is not in, put it in now.\n");
- X getreturn("to continue");
- X}
- X
- X/* Read configuration */
- Xvoid
- Xread_config_file() {
- X char tmp_ramdisk[PATHLEN], tmp_levels[PATHLEN];
- X char buf[BUFSZ], *bufp;
- X FILE *fp, *fopenp();
- X extern char plname[];
- X extern int saveprompt;
- X
- X tmp_ramdisk[0] = 0;
- X tmp_levels[0] = 0;
- X if ((fp = fopenp(configfile, "r")) == NULL) {
- X msmsg("Warning: no configuration file!\n");
- X getreturn("to continue");
- X return;
- X }
- X while (fgets(buf, BUFSZ, fp)) {
- X if (*buf == '#')
- X continue;
- X
- X /* remove trailing whitespace
- X */
- X bufp = index(buf, '\n');
- X while (bufp > buf && isspace(*bufp))
- X bufp--;
- X if (bufp == buf)
- X continue; /* skip all-blank lines */
- X else
- X *(bufp + 1) = 0; /* 0 terminate line */
- X
- X /* find the '=' */
- X if (!(bufp = strchr(buf, '='))) {
- X msmsg("Bad option line: '%s'\n", buf);
- X getreturn("to continue");
- X continue;
- X }
- X
- X /* skip whitespace between '=' and value */
- X while (isspace(*++bufp))
- X ;
- X
- X /* Go through possible variables */
- X if (!strncmp(buf, "HACKDIR", 4)) {
- X strncpy(hackdir, bufp, PATHLEN);
- X
- X } else if (!strncmp(buf, "RAMDISK", 3)) {
- X strncpy(tmp_ramdisk, bufp, PATHLEN);
- X
- X } else if (!strncmp(buf, "LEVELS", 4)) {
- X strncpy(tmp_levels, bufp, PATHLEN);
- X
- X } else if (!strncmp(buf, "OPTIONS", 4)) {
- X parseoptions(bufp, TRUE);
- X if (plname[0]) /* If a name was given */
- X plnamesuffix(); /* set the character class */
- X
- X } else if (!strncmp(buf, "SAVE", 4)) {
- X char *ptr;
- X if (ptr = index(bufp, ';')) {
- X *ptr = '\0';
- X if (*(ptr+1) == 'n' || *(ptr+1) == 'N')
- X saveprompt = FALSE;
- X }
- X (void) strncpy(SAVEF, bufp, PATHLEN);
- X append_slash(SAVEF);
- X
- X } else if (!strncmp(buf, "GRAPHICS", 4)) {
- X struct symbols s;
- X
- X if (sscanf(bufp, "%u%u%u%u%u%u%u%u%u", &s.vwall,
- X &s.hwall, &s.tlcorn, &s.trcorn, &s.blcorn,
- X &s.brcorn, &s.door, &s.room, &s.corr) == 9)
- X symbol = s;
- X else {
- X msmsg("GRAPHICS did not contain 9 values\n");
- X getreturn("to continue");
- X }
- X } else {
- X msmsg("Bad option line: '%s'\n", buf);
- X getreturn("to continue");
- X }
- X }
- X fclose(fp);
- X
- X strcpy(permbones, tmp_levels);
- X if (tmp_ramdisk[0]) {
- X strcpy(levels, tmp_ramdisk);
- X if (strcmpi(permbones, levels)) /* if not identical */
- X ramdisk = TRUE;
- X } else
- X strcpy(levels, tmp_levels);
- X strcpy(bones, levels);
- X}
- X
- X/* Set names for bones[] and lock[]
- X */
- Xvoid
- Xset_lock_and_bones() {
- X if (!ramdisk) {
- X strcpy(levels, permbones);
- X strcpy(bones, permbones);
- X }
- X append_slash(permbones);
- X append_slash(levels);
- X append_slash(bones);
- X strcat(bones, allbones);
- X strcpy(lock, levels);
- X strcat(lock, alllevels);
- X}
- X
- X/* Add a backslash to any name not ending in /, \ or : There must
- X * be room for the \
- X */
- Xvoid
- Xappend_slash(name)
- Xchar *name;
- X{
- X char *ptr;
- X
- X if (!*name)
- X return;
- X ptr = name + (strlen(name) - 1);
- X if (*ptr != '\\' && *ptr != '/' && *ptr != ':') {
- X *++ptr = '\\';
- X *++ptr = '\0';
- X }
- X}
- X
- X
- Xvoid
- Xgetreturn(str)
- Xchar *str;
- X{
- X int ch;
- X
- X msmsg("Hit <RETURN> %s.", str);
- X while ((ch = getchar()) != '\n')
- X ;
- X}
- X
- Xvoid
- Xmsmsg(fmt, a1, a2, a3)
- Xchar *fmt;
- Xlong a1, a2, a3;
- X{
- X printf(fmt, a1, a2, a3);
- X flushout();
- X}
- X
- X/* Chdrive() changes the default drive.
- X */
- X#define SELECTDISK 0x0E
- Xvoid
- Xchdrive(str)
- Xchar *str;
- X{
- X char *ptr;
- X union REGS inregs;
- X char drive;
- X
- X if ((ptr = index(str, ':')) != NULL) {
- X drive = toupper(*(ptr - 1));
- X inregs.h.ah = SELECTDISK;
- X inregs.h.dl = drive - 'A';
- X intdos(&inregs, &inregs);
- X }
- X}
- X
- X/* Use the IOCTL DOS function call to change stdin and stdout to raw
- X * mode. For stdin, this prevents MSDOS from trapping ^P, thus
- X * freeing us of ^P toggling 'echo to printer'.
- X * Thanks to Mark Zbikowski (markz@microsoft.UUCP).
- X */
- X
- X# define DEVICE 0x80
- X# define RAW 0x20
- X# define IOCTL 0x44
- X# define STDIN fileno(stdin)
- X# define STDOUT fileno(stdout)
- X# define GETBITS 0
- X# define SETBITS 1
- X
- Xstatic unsigned old_stdin, old_stdout, ioctl();
- X
- Xdisable_ctrlP() {
- X if (!flags.rawio)
- X return;
- X old_stdin = ioctl(STDIN, GETBITS, 0);
- X old_stdout = ioctl(STDOUT, GETBITS, 0);
- X if (old_stdin & DEVICE)
- X ioctl(STDIN, SETBITS, old_stdin | RAW);
- X if (old_stdout & DEVICE)
- X ioctl(STDOUT, SETBITS, old_stdout | RAW);
- X}
- X
- Xenable_ctrlP() {
- X if (!flags.rawio)
- X return;
- X if (old_stdin)
- X (void) ioctl(STDIN, SETBITS, old_stdin);
- X if (old_stdout)
- X (void) ioctl(STDOUT, SETBITS, old_stdout);
- X}
- X
- Xstatic unsigned
- Xioctl(handle, mode, setvalue)
- Xunsigned setvalue;
- X{
- X union REGS regs;
- X
- X regs.h.ah = IOCTL;
- X regs.h.al = mode;
- X regs.x.bx = handle;
- X regs.h.dl = setvalue;
- X regs.h.dh = 0; /* Zero out dh */
- X intdos(®s, ®s);
- X return (regs.x.dx);
- X}
- X
- X/* Follow the PATH, trying to fopen the file.
- X */
- X#define PATHSEP ';'
- X
- XFILE *
- Xfopenp(name, mode)
- Xchar *name, *mode;
- X{
- X char buf[BUFSIZ], *bp, *pp, *getenv(), lastch;
- X FILE *fp;
- X
- X /* Try the default directory first. Then look along PATH.
- X */
- X strcpy(buf, name);
- X if (fp = fopen(buf, mode))
- X return fp;
- X else {
- X pp = getenv("PATH");
- X while (pp && *pp) {
- X bp = buf;
- X while (*pp && *pp != PATHSEP)
- X lastch = *bp++ = *pp++;
- X if (lastch != '\\' && lastch != '/')
- X *bp++ = '\\';
- X strcpy(bp, name);
- X if (fp = fopen(buf, mode))
- X return fp;
- X if (*pp)
- X pp++;
- X }
- X }
- X return NULL;
- X}
- X# endif /* DGK */
- X
- X/* Chdir back to original directory
- X */
- X# undef exit
- Xvoid
- Xmsexit(code)
- X{
- X# ifdef CHDIR
- X extern char orgdir[];
- X# endif
- X
- X# ifdef DGK
- X flushout();
- X enable_ctrlP(); /* in case this wasn't done */
- X if (ramdisk)
- X copybones(TOPERM);
- X# endif
- X# ifdef CHDIR
- X chdir(orgdir); /* chdir, not chdirx */
- X# ifdef DGK
- X chdrive(orgdir);
- X# endif
- X# endif
- X exit(code);
- X}
- X#endif /* MSDOS */
- END_OF_msdos.c
- if test 13705 -ne `wc -c <msdos.c`; then
- echo shar: \"msdos.c\" unpacked with wrong size!
- fi
- # end of overwriting check
- fi
- if test -f objnam.c -a "${1}" != "-c" ; then
- echo shar: Will not over-write existing file \"objnam.c\"
- else
- echo shar: Extracting \"objnam.c\" \(13414 characters\)
- sed "s/^X//" >objnam.c <<'END_OF_objnam.c'
- X/* SCCS Id: @(#)objnam.c 1.3 87/07/14
- X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
- X/* objnam.c - version 1.0.2 */
- X
- X#include "hack.h"
- X#define Sprintf (void) sprintf
- X#define Strcat (void) strcat
- X#define Strcpy (void) strcpy
- X#define PREFIX 15
- Xextern char *eos();
- Xextern int bases[];
- X
- Xchar *
- Xstrprepend(s,pref) register char *s, *pref; {
- Xregister int i = strlen(pref);
- X if(i > PREFIX) {
- X pline("WARNING: prefix too short.");
- X return(s);
- X }
- X s -= i;
- X (void) strncpy(s, pref, i); /* do not copy trailing 0 */
- X return(s);
- X}
- X
- Xchar *
- Xsitoa(a) int a; {
- Xstatic char buf[13];
- X Sprintf(buf, (a < 0) ? "%d" : "+%d", a);
- X return(buf);
- X}
- X
- Xchar *
- Xtypename(otyp)
- Xregister int otyp;
- X{
- Xstatic char buf[BUFSZ];
- Xregister struct objclass *ocl = &objects[otyp];
- Xregister char *an = ocl->oc_name;
- Xregister char *dn = ocl->oc_descr;
- Xregister char *un = ocl->oc_uname;
- Xregister int nn = ocl->oc_name_known;
- X switch(ocl->oc_olet) {
- X case POTION_SYM:
- X Strcpy(buf, "potion");
- X break;
- X case SCROLL_SYM:
- X Strcpy(buf, "scroll");
- X break;
- X case WAND_SYM:
- X Strcpy(buf, "wand");
- X break;
- X#ifdef SPELLS
- X case SPBOOK_SYM:
- X Strcpy(buf, "spellbook");
- X break;
- X#endif
- X case RING_SYM:
- X Strcpy(buf, "ring");
- X break;
- X default:
- X if(nn) {
- X Strcpy(buf, an);
- X if(otyp >= TURQUOISE && otyp <= JADE)
- X Strcat(buf, " stone");
- X if(un)
- X Sprintf(eos(buf), " called %s", un);
- X if(dn)
- X Sprintf(eos(buf), " (%s)", dn);
- X } else {
- X Strcpy(buf, dn ? dn : an);
- X if(ocl->oc_olet == GEM_SYM)
- X Strcat(buf, " gem");
- X if(un)
- X Sprintf(eos(buf), " called %s", un);
- X }
- X return(buf);
- X }
- X /* here for ring/scroll/potion/wand */
- X if(nn)
- X Sprintf(eos(buf), " of %s", an);
- X if(un)
- X Sprintf(eos(buf), " called %s", un);
- X if(dn)
- X Sprintf(eos(buf), " (%s)", dn);
- X return(buf);
- X}
- X
- Xchar *
- Xxname(obj)
- Xregister struct obj *obj;
- X{
- Xstatic char bufr[BUFSZ];
- Xregister char *buf = &(bufr[PREFIX]); /* leave room for "17 -3 " */
- Xregister int nn = objects[obj->otyp].oc_name_known;
- Xregister char *an = objects[obj->otyp].oc_name;
- Xregister char *dn = objects[obj->otyp].oc_descr;
- Xregister char *un = objects[obj->otyp].oc_uname;
- Xregister int pl = (obj->quan != 1);
- X#ifdef KAA
- X if(!obj->dknown && !Blind && obj->olet != WEAPON_SYM) obj->dknown=1;
- X#else
- X if(!obj->dknown && !Blind) obj->dknown = 1; /* %% doesnt belong here */
- X#endif
- X switch(obj->olet) {
- X case AMULET_SYM:
- X Strcpy(buf, (obj->spe < 0 && obj->known)
- X ? "cheap plastic imitation of the " : "");
- X Strcat(buf,"Amulet of Yendor");
- X break;
- X case TOOL_SYM:
- X if(!nn) {
- X Strcpy(buf, dn);
- X break;
- X }
- X Strcpy(buf,an);
- X break;
- X case FOOD_SYM:
- X if(obj->otyp == DEAD_HOMUNCULUS && pl) {
- X pl = 0;
- X Strcpy(buf, "dead homunculi");
- X break;
- X }
- X /* fungis ? */
- X#ifdef KAA /* The fungus mistake was a D&D holdover. */
- X if(obj->otyp == DEAD_VIOLET_FUNGUS && pl) {
- X pl = 0;
- X Strcpy(buf, "dead violet fungi");
- X break;
- X }
- X#endif
- X /* fall into next case */
- X case WEAPON_SYM:
- X if(obj->otyp == WORM_TOOTH && pl) {
- X pl = 0;
- X Strcpy(buf, "worm teeth");
- X break;
- X }
- X if(obj->otyp == CRYSKNIFE && pl) {
- X pl = 0;
- X Strcpy(buf, "crysknives");
- X break;
- X }
- X /* fall into next case */
- X case ARMOR_SYM:
- X case CHAIN_SYM:
- X case ROCK_SYM:
- X Strcpy(buf,an);
- X break;
- X case BALL_SYM:
- X Sprintf(buf, "%sheavy iron ball",
- X (obj->owt > objects[obj->otyp].oc_weight) ? "very " : "");
- X break;
- X case POTION_SYM:
- X if(nn || un || !obj->dknown) {
- X Strcpy(buf, "potion");
- X if(pl) {
- X pl = 0;
- X Strcat(buf, "s");
- X }
- X if(!obj->dknown) break;
- X if(un) {
- X Strcat(buf, " called ");
- X Strcat(buf, un);
- X } else {
- X Strcat(buf, " of ");
- X Strcat(buf, an);
- X }
- X } else {
- X Strcpy(buf, dn);
- X Strcat(buf, " potion");
- X }
- X break;
- X case SCROLL_SYM:
- X Strcpy(buf, "scroll");
- X if(pl) {
- X pl = 0;
- X Strcat(buf, "s");
- X }
- X if(!obj->dknown) break;
- X if(nn) {
- X Strcat(buf, " of ");
- X Strcat(buf, an);
- X } else if(un) {
- X Strcat(buf, " called ");
- X Strcat(buf, un);
- X } else {
- X Strcat(buf, " labeled ");
- X Strcat(buf, dn);
- X }
- X break;
- X case WAND_SYM:
- X if(!obj->dknown)
- X Sprintf(buf, "wand");
- X else if(nn)
- X Sprintf(buf, "wand of %s", an);
- X else if(un)
- X Sprintf(buf, "wand called %s", un);
- X else
- X Sprintf(buf, "%s wand", dn);
- X break;
- X#ifdef SPELLS
- X case SPBOOK_SYM:
- X if(!obj->dknown)
- X Sprintf(buf, "spellbook");
- X else if(nn)
- X Sprintf(buf, "spellbook of %s", an);
- X else if(un)
- X Sprintf(buf, "spellbook called %s", un);
- X else
- X Sprintf(buf, "%s spellbook", dn);
- X break;
- X#endif
- X case RING_SYM:
- X if(!obj->dknown)
- X Sprintf(buf, "ring");
- X else if(nn)
- X Sprintf(buf, "ring of %s", an);
- X else if(un)
- X Sprintf(buf, "ring called %s", un);
- X else
- X Sprintf(buf, "%s ring", dn);
- X break;
- X case GEM_SYM:
- X if(!obj->dknown) {
- X Strcpy(buf, "gem");
- X break;
- X }
- X if(!nn) {
- X#ifdef KAA
- X if(un) {
- X if (!pl) Sprintf(buf,"gem called %s",un);
- X else Sprintf(buf,"gems called %s",un);
- X pl=0;
- X } else
- X#endif
- X Sprintf(buf, "%s gem", dn);
- X break;
- X }
- X Strcpy(buf, an);
- X if(obj->otyp >= TURQUOISE && obj->otyp <= JADE)
- X Strcat(buf, " stone");
- X break;
- X default:
- X Sprintf(buf,"glorkum %c (0%o) %u %d",
- X obj->olet,obj->olet,obj->otyp,obj->spe);
- X }
- X if(pl) {
- X register char *p;
- X
- X for(p = buf; *p; p++) {
- X if(!strncmp(" of ", p, 4)) {
- X /* pieces of, cloves of, lumps of */
- X register int c1, c2 = 's';
- X
- X do {
- X c1 = c2; c2 = *p; *p++ = c1;
- X } while(c1);
- X goto nopl;
- X }
- X }
- X p = eos(buf)-1;
- X if(*p == 's' || *p == 'z' || *p == 'x' ||
- X (*p == 'h' && p[-1] == 's'))
- X Strcat(buf, "es"); /* boxes */
- X else if(*p == 'y' && !index(vowels, p[-1]))
- X Strcpy(p, "ies"); /* rubies, zruties */
- X else
- X Strcat(buf, "s");
- X }
- Xnopl:
- X if(obj->onamelth) {
- X Strcat(buf, " named ");
- X Strcat(buf, ONAME(obj));
- X }
- X return(buf);
- X}
- X
- Xchar *
- Xdoname(obj)
- Xregister struct obj *obj;
- X{
- Xchar prefix[PREFIX];
- Xregister char *bp = xname(obj);
- X if(obj->quan != 1)
- X Sprintf(prefix, "%u ", obj->quan);
- X else
- X Strcpy(prefix, "a ");
- X switch(obj->olet) {
- X case AMULET_SYM:
- X if(strncmp(bp, "cheap ", 6))
- X Strcpy(prefix, "the ");
- X break;
- X case ARMOR_SYM:
- X if(obj->owornmask & W_ARMOR)
- X Strcat(bp, " (being worn)");
- X /* fall into next case */
- X case WEAPON_SYM:
- X if(obj->known) {
- X#ifdef KAA
- X /* dknown is special for weapons */
- X if(obj->dknown && obj->olet == WEAPON_SYM)
- X Strcat(prefix,"blessed ");
- X#endif
- X Strcat(prefix, sitoa(obj->spe));
- X Strcat(prefix, " ");
- X }
- X break;
- X#ifdef MARKER
- X case TOOL_SYM: /* temp. hack by GAN 11/18/86 */
- X if(obj->otyp != MAGIC_MARKER) break;
- X#endif
- X case WAND_SYM:
- X if(obj->known)
- X Sprintf(eos(bp), " (%d)", obj->spe);
- X break;
- X case RING_SYM:
- X if(obj->owornmask & W_RINGR) Strcat(bp, " (on right hand)");
- X if(obj->owornmask & W_RINGL) Strcat(bp, " (on left hand)");
- X if(obj->known && (objects[obj->otyp].bits & SPEC)) {
- X Strcat(prefix, sitoa(obj->spe));
- X Strcat(prefix, " ");
- X }
- X break;
- X }
- X if(obj->owornmask & W_WEP)
- X Strcat(bp, " (weapon in hand)");
- X if(obj->unpaid)
- X Strcat(bp, " (unpaid)");
- X if(!strcmp(prefix, "a ") && index(vowels, *bp))
- X Strcpy(prefix, "an ");
- X bp = strprepend(bp, prefix);
- X return(bp);
- X}
- X
- X/* used only in fight.c (thitu) */
- Xsetan(str,buf)
- Xregister char *str,*buf;
- X{
- X if(index(vowels,*str))
- X Sprintf(buf, "an %s", str);
- X else
- X Sprintf(buf, "a %s", str);
- X}
- X
- Xchar *
- Xaobjnam(otmp,verb) register struct obj *otmp; register char *verb; {
- Xregister char *bp = xname(otmp);
- Xchar prefix[PREFIX];
- X if(otmp->quan != 1) {
- X Sprintf(prefix, "%u ", otmp->quan);
- X bp = strprepend(bp, prefix);
- X }
- X
- X if(verb) {
- X /* verb is given in plural (i.e., without trailing s) */
- X Strcat(bp, " ");
- X if(otmp->quan != 1)
- X Strcat(bp, verb);
- X else if(!strcmp(verb, "are"))
- X Strcat(bp, "is");
- X else {
- X Strcat(bp, verb);
- X Strcat(bp, "s");
- X }
- X }
- X return(bp);
- X}
- X
- Xchar *
- XDoname(obj)
- Xregister struct obj *obj;
- X{
- X register char *s = doname(obj);
- X
- X if('a' <= *s && *s <= 'z') *s -= ('a' - 'A');
- X return(s);
- X}
- X
- Xchar *wrp[] = { "wand", "ring", "potion", "scroll", "gem"
- X#ifdef SPELLS
- X , "spellbook"
- X#endif
- X };
- Xchar wrpsym[] = { WAND_SYM, RING_SYM, POTION_SYM, SCROLL_SYM, GEM_SYM
- X#ifdef SPELLS
- X , SPBOOK_SYM
- X#endif
- X };
- X
- Xstruct obj *
- Xreadobjnam(bp) register char *bp; {
- Xregister char *p;
- Xregister int i;
- Xint cnt, spe, spesgn, typ, heavy;
- Xchar let;
- Xchar *un, *dn, *an;
- X#ifdef KAA
- Xint blessed=0;
- X#endif
- X/* int the = 0; char *oname = 0; */
- X cnt = spe = spesgn = typ = heavy = 0;
- X let = 0;
- X an = dn = un = 0;
- X for(p = bp; *p; p++) /* set the string to lower case */
- X if('A' <= *p && *p <= 'Z') *p += 'a'-'A';
- X if(!strncmp(bp, "the ", 4)){
- X/* the = 1; */
- X bp += 4;
- X } else if(!strncmp(bp, "an ", 3)){
- X cnt = 1;
- X bp += 3;
- X } else if(!strncmp(bp, "a ", 2)){
- X cnt = 1;
- X bp += 2;
- X }
- X#ifdef KAA
- X if(!strncmp(bp,"blessed ",8)) {
- X blessed=1;
- X bp += 8;
- X }
- X#endif
- X if(!cnt && digit(*bp)){
- X cnt = atoi(bp);
- X while(digit(*bp)) bp++;
- X while(*bp == ' ') bp++;
- X }
- X if(!cnt) cnt = 1; /* %% what with "gems" etc. ? */
- X
- X if(*bp == '+' || *bp == '-'){
- X spesgn = (*bp++ == '+') ? 1 : -1;
- X spe = atoi(bp);
- X while(digit(*bp)) bp++;
- X while(*bp == ' ') bp++;
- X } else {
- X p = rindex(bp, '(');
- X if(p) {
- X if(p > bp && p[-1] == ' ') p[-1] = 0;
- X else *p = 0;
- X p++;
- X spe = atoi(p);
- X while(digit(*p)) p++;
- X if(strcmp(p, ")")) spe = 0;
- X else spesgn = 1;
- X }
- X }
- X /* now we have the actual name, as delivered by xname, say
- X green potions called whisky
- X scrolls labeled "QWERTY"
- X egg
- X dead zruties
- X fortune cookies
- X very heavy iron ball named hoei
- X wand of wishing
- X elven cloak
- X */
- X for(p = bp; *p; p++) if(!strncmp(p, " named ", 7)) {
- X *p = 0;
- X/* oname = p+7; */
- X }
- X for(p = bp; *p; p++) if(!strncmp(p, " called ", 8)) {
- X *p = 0;
- X un = p+8;
- X }
- X for(p = bp; *p; p++) if(!strncmp(p, " labeled ", 9)) {
- X *p = 0;
- X dn = p+9;
- X }
- X
- X /* first change to singular if necessary */
- X if(cnt != 1) {
- X /* find "cloves of garlic", "worthless pieces of blue glass" */
- X for(p = bp; *p; p++) if(!strncmp(p, "s of ", 5)){
- X while(*p = p[1]) p++;
- X goto sing;
- X }
- X /* remove -s or -es (boxes) or -ies (rubies, zruties) */
- X p = eos(bp);
- X if(p[-1] == 's') {
- X if(p[-2] == 'e') {
- X if(p[-3] == 'i') {
- X#ifdef KAA
- X if(!strcmp(p-7, "cookies") || !strcmp(p-4, "pies"))
- X#else
- X if(!strcmp(p-7, "cookies"))
- X#endif
- X goto mins;
- X Strcpy(p-3, "y");
- X goto sing;
- X }
- X
- X /* note: cloves / knives from clove / knife */
- X if(!strcmp(p-6, "knives")) {
- X Strcpy(p-3, "fe");
- X goto sing;
- X }
- X
- X /* note: nurses, axes but boxes */
- X if(!strcmp(p-5, "boxes")) {
- X p[-2] = 0;
- X goto sing;
- X }
- X }
- X mins:
- X p[-1] = 0;
- X } else {
- X if(!strcmp(p-9, "homunculi")
- X#ifdef KAA
- X || !strcmp(p-5, "fungi")
- X#endif
- X ) {
- X Strcpy(p-1, "us"); /* !! makes string longer */
- X goto sing;
- X }
- X if(!strcmp(p-5, "teeth")) {
- X Strcpy(p-5, "tooth");
- X goto sing;
- X }
- X /* here we cannot find the plural suffix */
- X }
- X }
- Xsing:
- X if(!strcmp(bp, "amulet of yendor")) {
- X typ = AMULET_OF_YENDOR;
- X goto typfnd;
- X }
- X if(!strcmp(bp, "ring mail")){ /* Note: ring mail is not a ring ! */
- X let = ARMOR_SYM;
- X an = bp;
- X goto srch;
- X }
- X
- X p = eos(bp);
- X#ifdef KOPS /* kluge to re-capitalize "dead Kop" */
- X if (!strcmp(p-3, "kop")) {
- X *(p-3) = 'K';
- X an = bp;
- X goto srch;
- X }
- X#endif
- X
- X for(i = 0; i < sizeof(wrpsym); i++) {
- X register int j = strlen(wrp[i]);
- X if(!strncmp(bp, wrp[i], j)){
- X let = wrpsym[i];
- X bp += j;
- X if(!strncmp(bp, " of ", 4)) an = bp+4;
- X /* else if(*bp) ?? */
- X goto srch;
- X }
- X if(!strcmp(p-j, wrp[i])){
- X let = wrpsym[i];
- X p -= j;
- X *p = 0;
- X if(p[-1] == ' ') p[-1] = 0;
- X dn = bp;
- X goto srch;
- X }
- X }
- X if(!strcmp(p-6, " stone")){
- X p[-6] = 0;
- X let = GEM_SYM;
- X an = bp;
- X goto srch;
- X }
- X#ifdef KAA
- X if(!strcmp(p-10, "gold piece") || !strcmp(p-7, "zorkmid")) {
- X if (cnt > 5000) cnt=5000;
- X if (cnt < 1) cnt=1;
- X pline("%d gold piece%s.", cnt, cnt==1 ? "" : "s");
- X u.ugold += cnt;
- X flags.botl=1;
- X return(0);
- X }
- X#endif
- X if(!strcmp(bp, "very heavy iron ball")){
- X heavy = 1;
- X typ = HEAVY_IRON_BALL;
- X goto typfnd;
- X }
- X an = bp;
- Xsrch:
- X if(!an && !dn && !un)
- X goto any;
- X i = 1;
- X if(let) i = bases[letindex(let)];
- X while(i <= NROFOBJECTS && (!let || objects[i].oc_olet == let)){
- X register char *zn = objects[i].oc_name;
- X
- X if(!zn) goto nxti;
- X if(an && strcmp(an, zn))
- X goto nxti;
- X if(dn && (!(zn = objects[i].oc_descr) || strcmp(dn, zn)))
- X goto nxti;
- X if(un && (!(zn = objects[i].oc_uname) || strcmp(un, zn)))
- X goto nxti;
- X typ = i;
- X goto typfnd;
- X nxti:
- X i++;
- X }
- Xany:
- X if(!let) let = wrpsym[rn2(sizeof(wrpsym))];
- X typ = probtype(let);
- Xtypfnd:
- X { register struct obj *otmp;
- X extern struct obj *mksobj();
- X let = objects[typ].oc_olet;
- X otmp = mksobj(typ);
- X if(heavy)
- X otmp->owt += 15;
- X if(cnt > 0 && index("%?!*)", let) &&
- X#ifdef KAA
- X (cnt < 4 || (let == WEAPON_SYM && typ <= ROCK && cnt <= 20)))
- X#else
- X (cnt < 4 || (let == WEAPON_SYM && typ <= ROCK && cnt < 20)))
- X#endif
- X otmp->quan = cnt;
- X
- X if(spe > 3 && spe > otmp->spe)
- X spe = 0;
- X else if(let == WAND_SYM)
- X spe = otmp->spe;
- X#ifdef KAA
- X if(let==WEAPON_SYM && blessed) {
- X if(u.uluck < 0) otmp->cursed=1;
- X else otmp->dknown=1;
- X }
- X#endif
- X if(spe == 3 && u.uluck < 0)
- X spesgn = -1;
- X if(let != WAND_SYM && spesgn == -1)
- X spe = -spe;
- X if(let == BALL_SYM)
- X spe = 0;
- X else if(let == AMULET_SYM)
- X spe = -1;
- X else if(typ == WAN_WISHING && rn2(10))
- X spe = (rn2(10) ? -1 : 0);
- X#ifdef MARKER
- X else if(typ == MAGIC_MARKER)
- X spe = rn1(50,50);
- X#endif
- X otmp->spe = spe;
- X
- X if(spesgn == -1)
- X otmp->cursed = 1;
- X
- X return(otmp);
- X }
- X}
- END_OF_objnam.c
- if test 13414 -ne `wc -c <objnam.c`; then
- echo shar: \"objnam.c\" unpacked with wrong size!
- fi
- # end of overwriting check
- fi
- if test -f potion.c -a "${1}" != "-c" ; then
- echo shar: Will not over-write existing file \"potion.c\"
- else
- echo shar: Extracting \"potion.c\" \(13424 characters\)
- sed "s/^X//" >potion.c <<'END_OF_potion.c'
- X/* SCCS Id: @(#)potion.c 1.3 87/07/14
- X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
- X/* potion.c - version 1.0.3 */
- X
- X#include "hack.h"
- Xextern int float_down();
- Xextern char *nomovemsg;
- Xextern struct monst youmonst;
- Xextern struct monst *makemon();
- Xchar *hcolor();
- X#ifdef KAA
- Xchar *xname();
- Xextern char pl_character[];
- X#endif
- X#ifdef FOUNTAINS
- Xextern int drinkfountain();
- Xextern int dipfountain();
- X#endif
- X
- Xint nothing, unkn;
- X
- Xdodrink() {
- X register struct obj *otmp;
- X register int retval;
- X
- X#ifdef FOUNTAINS
- X
- X /* Is there something to drink here, i.e., a fountain? */
- X if (IS_FOUNTAIN(levl[u.ux][u.uy].typ)) {
- X pline("Drink from the fountain? [ny] ");
- X if(readchar() == 'y') {
- X (void) drinkfountain();
- X return(0);
- X }
- X }
- X
- X#endif /* FOUNTAINS /**/
- X
- X nothing = unkn = 0;
- X otmp = getobj("!", "drink");
- X if(!otmp) return(0);
- X if(!strcmp(objects[otmp->otyp].oc_descr, "smoky") && !rn2(13)) {
- X ghost_from_bottle();
- X goto use_it;
- X }
- X if((retval = peffects(otmp)) >= 0) return(retval);
- X
- X if(nothing) {
- X unkn++;
- X pline("You have a %s feeling for a moment, then it passes.",
- X Hallucination ? "normal" : "peculiar");
- X }
- X if(otmp->dknown && !objects[otmp->otyp].oc_name_known) {
- X if(!unkn) {
- X objects[otmp->otyp].oc_name_known = 1;
- X more_experienced(0,10);
- X } else if(!objects[otmp->otyp].oc_uname)
- X docall(otmp);
- X }
- Xuse_it:
- X useup(otmp);
- X return(1);
- X}
- X
- Xpeffects(otmp)
- X register struct obj *otmp;
- X{
- X register struct obj *objs;
- X register struct monst *mtmp;
- X
- X switch(otmp->otyp){
- X case POT_RESTORE_STRENGTH:
- X#ifdef SPELLS
- X case SPE_RESTORE_STRENGTH:
- X#endif
- X unkn++;
- X pline("Wow! This makes you feel great!");
- X if(u.ustr < u.ustrmax) {
- X u.ustr = u.ustrmax;
- X flags.botl = 1;
- X }
- X break;
- X#ifdef KAA
- X case POT_HALLUCINATION:
- X if (Hallucination) nothing++;
- X else pline("Oh wow! Everything looks so cosmic!");
- X Hallucination += rn1(100,750);
- X setsee();
- X break;
- X case POT_HOLY_WATER:
- X unkn++;
- X if(index("VWZ&",u.usym)) {
- X pline("This burns like acid!");
- X losehp(d(2,6)); /* will never kill you */
- X } else {
- X pline("You feel full of awe.");
- X if (Sick) Sick=0;
- X if (HConfusion) HConfusion=0;
- X }
- X#else
- X case POT_HOLY_WATER:
- X case POT_HALLUCINATION:
- X#endif
- X break;
- X case POT_BOOZE:
- X unkn++;
- X pline("Ooph! This tastes like liquid fire!");
- X HConfusion += d(3,8);
- X /* the whiskey makes us feel better */
- X if(u.uhp < u.uhpmax) losehp(-1, "bottle of whiskey");
- X if(!rn2(4)) {
- X pline("You pass out.");
- X multi = -rnd(15);
- X nomovemsg = "You awake with a headache.";
- X }
- X break;
- X case POT_INVISIBILITY:
- X#ifdef SPELLS
- X case SPE_INVISIBILITY:
- X#endif
- X if(Invis || See_invisible)
- X nothing++;
- X else {
- X if(!Blind)
- X pline("Gee! All of a sudden, you can't see yourself.");
- X else
- X pline("You feel rather airy."), unkn++;
- X newsym(u.ux,u.uy);
- X }
- X HInvis += rn1(15,31);
- X break;
- X case POT_FRUIT_JUICE:
- X pline("This tastes like fruit juice.");
- X lesshungry(20);
- X break;
- X case POT_HEALING:
- X pline("You begin to feel better.");
- X healup(rnd(10), 1, 1, 1);
- X break;
- X case POT_PARALYSIS:
- X if(Levitation)
- X pline("You are motionlessly suspended.");
- X else
- X pline("Your feet are frozen to the floor!");
- X nomul(-(rn1(10,25)));
- X break;
- X case POT_MONSTER_DETECTION:
- X#ifdef SPELLS
- X case SPE_DETECT_MONSTERS:
- X#endif
- X if(!fmon) {
- X strange_feeling(otmp, "You feel threatened.");
- X return(1);
- X } else {
- X cls();
- X for(mtmp = fmon; mtmp; mtmp = mtmp->nmon)
- X if(mtmp->mx > 0)
- X at(mtmp->mx,mtmp->my,Hallucination ? rndmonsym() :
- X mtmp->data->mlet);
- X prme();
- X pline("You sense the presence of monsters.");
- X more();
- X docrt();
- X }
- X break;
- X case POT_OBJECT_DETECTION:
- X#ifdef SPELLS
- X case SPE_DETECT_TREASURE:
- X#endif
- X if(!fobj) {
- X strange_feeling(otmp, "You feel a pull downward.");
- X return(1);
- X } else {
- X for(objs = fobj; objs; objs = objs->nobj)
- X if(objs->ox != u.ux || objs->oy != u.uy)
- X goto outobjmap;
- X pline("You sense the presence of objects close nearby.");
- X break;
- X outobjmap:
- X cls();
- X for(objs = fobj; objs; objs = objs->nobj)
- X at(objs->ox,objs->oy,Hallucination ? rndobjsym()
- X : objs->olet);
- X
- X /* monster possessions added by GAN 12/16/86 */
- X for(mtmp = fmon ; mtmp ; mtmp = mtmp->nmon)
- X if(mtmp->minvent)
- X for(objs = mtmp->minvent; objs ;
- X objs = objs->nobj)
- X at(mtmp->mx,mtmp->my,objs->olet);
- X prme();
- X pline("You sense the presence of objects.");
- X more();
- X docrt();
- X }
- X break;
- X case POT_SICKNESS:
- X pline("Yech! This stuff tastes like poison.");
- X if(Poison_resistance)
- X pline("(But in fact it was biologically contaminated orange juice.)");
- X#ifdef KAA
- X if (pl_character[0] == 'H')
- X pline("Fortunately you have been immunized!");
- X else {
- X#endif
- X losestr(rn1(4,3));
- X losehp(rnd(10), "contaminated potion");
- X#ifdef KAA
- X }
- X#endif
- X if(Hallucination) {
- X pline("You are shocked back to your senses!");
- X Hallucination=1;
- X }
- X break;
- X case POT_CONFUSION:
- X if(!Confusion)
- X if (Hallucination) {
- X pline("What a trippy feeling!");
- X unkn++;
- X } else
- X pline("Huh, What? Where am I?");
- X else nothing++;
- X HConfusion += rn1(7,16);
- X break;
- X case POT_GAIN_STRENGTH:
- X pline("Wow do you feel strong!");
- X gainstr(0);
- X break;
- X case POT_SPEED:
- X if(Wounded_legs) {
- X heal_legs();
- X unkn++;
- X break;
- X } /* and fall through */
- X#ifdef SPELLS
- X case SPE_HASTE_SELF:
- X#endif
- X if(!(Fast & ~INTRINSIC))
- X pline("You are suddenly moving much faster.");
- X else
- X pline("Your legs get new energy."), unkn++;
- X Fast += rn1(10,100);
- X break;
- X case POT_BLINDNESS:
- X if(!Blind)
- X if (Hallucination)
- X pline("Bummer! Everything is dark! Help!");
- X else
- X pline("A cloud of darkness falls upon you.");
- X else nothing++;
- X Blind += rn1(100,250);
- X seeoff(0);
- X break;
- X case POT_GAIN_LEVEL:
- X pluslvl();
- X break;
- X case POT_EXTRA_HEALING:
- X pline("You feel much better.");
- X healup(d(2,20)+1, 2, 1, 1);
- X if(Hallucination) Hallucination = 1;
- X break;
- X case POT_LEVITATION:
- X#ifdef SPELLS
- X case SPE_LEVITATION:
- X#endif
- X if(!Levitation)
- X float_up();
- X else
- X nothing++;
- X Levitation += rnd(100);
- X u.uprops[PROP(RIN_LEVITATION)].p_tofn = float_down;
- X break;
- X case POT_GAIN_ENERGY: /* M. Stephenson */
- X#ifdef SPELLS
- X { register int num;
- X if(Confusion) {
- X pline("You feel feverish.");
- X unkn++;
- X } else
- X pline("Magical energies course through your body.");
- X num = rnd(5) + 1;
- X u.uenmax += num;
- X u.uen += num;
- X flags.botl = 1;
- X break;
- X }
- X#else
- X pline("This potion tastes wierd!");
- X break;
- X#endif
- X default:
- X impossible("What a funny potion! (%u)", otmp->otyp);
- X return(0);
- X }
- X return(-1);
- X}
- X
- Xhealup(nhp, nxtra, curesick, cureblind)
- X int nhp, nxtra;
- X register boolean curesick, cureblind;
- X{
- X#ifdef KAA
- X if (u.mtimedone & nhp) {
- X u.mh += rnd(nhp);
- X if (u.mh > u.mhmax) u.mh = ++u.mhmax;
- X }
- X#endif
- X if(nhp) {
- X u.uhp += nhp;
- X if(u.uhp > u.uhpmax) u.uhp = (u.uhpmax += nxtra);
- X }
- X if(Blind && cureblind) Blind = 1; /* see on next move */
- X if(Sick && curesick) Sick = 0;
- X flags.botl = 1;
- X return;
- X}
- X
- Xpluslvl()
- X{
- X register num;
- X
- X pline("You feel more experienced.");
- X num = rnd(10);
- X u.uhpmax += num;
- X u.uhp += num;
- X#ifdef SPELLS
- X num = rnd(u.ulevel/2+1) + 1; /* M. Stephenson */
- X u.uenmax += num;
- X u.uen += num;
- X#endif
- X if(u.ulevel < 14) {
- X extern long newuexp();
- X
- X u.uexp = newuexp()+1;
- X pline("Welcome to experience level %u.", ++u.ulevel);
- X }
- X flags.botl = 1;
- X}
- X
- Xstrange_feeling(obj,txt)
- Xregister struct obj *obj;
- Xregister char *txt;
- X{
- X if(flags.beginner)
- X pline("You have a %s feeling for a moment, then it passes.",
- X Hallucination ? "normal" : "strange");
- X else
- X pline(txt);
- X if(!objects[obj->otyp].oc_name_known && !objects[obj->otyp].oc_uname)
- X docall(obj);
- X useup(obj);
- X}
- X
- Xchar *bottlenames[] = {
- X "bottle", "phial", "flagon", "carafe", "flask", "jar", "vial"
- X};
- X
- Xpotionhit(mon, obj)
- Xregister struct monst *mon;
- Xregister struct obj *obj;
- X{
- X extern char *xname();
- X register char *botlnam = bottlenames[rn2(SIZE(bottlenames))];
- X boolean uclose, isyou = (mon == &youmonst);
- X
- X if(isyou) {
- X uclose = TRUE;
- X pline("The %s crashes on your head and breaks into shivers.",
- X botlnam);
- X losehp(rnd(2), "thrown potion");
- X } else {
- X uclose = (dist(mon->mx,mon->my) < 3);
- X /* perhaps 'E' and 'a' have no head? */
- X pline("The %s crashes on %s's head and breaks into shivers.",
- X botlnam, monnam(mon));
- X if(rn2(5) && mon->mhp > 1)
- X mon->mhp--;
- X }
- X pline("The %s evaporates.", xname(obj));
- X
- X#ifdef KAA
- X if(!isyou) switch (obj->otyp) {
- X#else
- X if(!isyou && !rn2(3)) switch(obj->otyp) {
- X#endif
- X
- X case POT_RESTORE_STRENGTH:
- X case POT_GAIN_STRENGTH:
- X case POT_HEALING:
- X case POT_EXTRA_HEALING:
- X if(mon->mhp < mon->mhpmax) {
- X mon->mhp = mon->mhpmax;
- X pline("%s looks sound and hale again!", Monnam(mon));
- X }
- X break;
- X case POT_SICKNESS:
- X if((mon->mhpmax > 3) && !resist(mon, '!', 0, NOTELL))
- X mon->mhpmax /= 2;
- X if((mon->mhp > 2) && !resist(mon, '!', 0, NOTELL))
- X mon->mhp /= 2;
- X#ifdef KAA
- X pline("%s looks rather ill.", Monnam(mon));
- X#endif
- X break;
- X case POT_CONFUSION:
- X case POT_BOOZE:
- X if(!resist(mon, '!', 0, NOTELL)) mon->mconf = 1;
- X break;
- X case POT_INVISIBILITY:
- X unpmon(mon);
- X mon->minvis = 1;
- X pmon(mon);
- X break;
- X case POT_PARALYSIS:
- X mon->mfroz = 1;
- X break;
- X case POT_SPEED:
- X mon->mspeed = MFAST;
- X break;
- X case POT_BLINDNESS:
- X mon->mblinded |= 64 + rn2(32) +
- X rn2(32) * !resist(mon, '!', 0, NOTELL);
- X break;
- X#ifdef KAA
- X case POT_HOLY_WATER:
- X if (index("ZVW &", mon->data->mlet)) {
- X pline("%s shrieks in pain!", Monnam(mon));
- X mon->mhp -= d(2,6);
- X if (mon->mhp <1) killed(mon);
- X }
- X break;
- X#endif
- X/*
- X case POT_GAIN_LEVEL:
- X case POT_LEVITATION:
- X case POT_FRUIT_JUICE:
- X case POT_MONSTER_DETECTION:
- X case POT_OBJECT_DETECTION:
- X break;
- X*/
- X }
- X if(uclose && rn2(5))
- X potionbreathe(obj);
- X obfree(obj, Null(obj));
- X}
- X
- Xpotionbreathe(obj)
- Xregister struct obj *obj;
- X{
- X switch(obj->otyp) {
- X case POT_RESTORE_STRENGTH:
- X case POT_GAIN_STRENGTH:
- X if(u.ustr < u.ustrmax) u.ustr++, flags.botl = 1;
- X break;
- X case POT_HEALING:
- X case POT_EXTRA_HEALING:
- X if(u.uhp < u.uhpmax) u.uhp++, flags.botl = 1;
- X break;
- X case POT_SICKNESS:
- X if(u.uhp <= 5) u.uhp = 1; else u.uhp -= 5;
- X flags.botl = 1;
- X break;
- X case POT_HALLUCINATION:
- X#ifdef KAA
- X pline("You have a vision for a moment.");
- X break;
- X#endif
- X case POT_CONFUSION:
- X case POT_BOOZE:
- X if(!Confusion)
- X pline("You feel somewhat dizzy.");
- X HConfusion += rnd(5);
- X break;
- X case POT_INVISIBILITY:
- X pline("For an instant you couldn't see your right hand.");
- X break;
- X case POT_PARALYSIS:
- X pline("Something seems to be holding you.");
- X nomul(-rnd(5));
- X break;
- X case POT_SPEED:
- X Fast += rnd(5);
- X pline("Your knees seem more flexible now.");
- X break;
- X case POT_BLINDNESS:
- X if(!Blind) pline("It suddenly gets dark.");
- X Blind += rnd(5);
- X seeoff(0);
- X break;
- X/*
- X case POT_GAIN_LEVEL:
- X case POT_LEVITATION:
- X case POT_FRUIT_JUICE:
- X case POT_MONSTER_DETECTION:
- X case POT_OBJECT_DETECTION:
- X break;
- X*/
- X }
- X /* note: no obfree() */
- X}
- X
- X/*
- X * -- rudimentary -- to do this correctly requires much more work
- X * -- all sharp weapons get one or more qualities derived from the potions
- X * -- texts on scrolls may be (partially) wiped out; do they become blank?
- X * -- or does their effect change, like under Confusion?
- X * -- all objects may be made invisible by POT_INVISIBILITY
- X * -- If the flask is small, can one dip a large object? Does it magically
- X * -- become a jug? Etc.
- X */
- Xdodip(){
- X register struct obj *potion, *obj;
- X#ifdef KAA
- X char *tmp;
- X#endif
- X
- X if(!(obj = getobj("#", "dip")))
- X return(0);
- X#ifdef FOUNTAINS
- X /* Is there something to dip into here, i.e., a fountain? */
- X if (levl[u.ux][u.uy].typ == FOUNTAIN) {
- X pline("Dip it in the fountain? [ny] ");
- X if(readchar() == 'y') {
- X dipfountain(obj);
- X return(1);
- X }
- X }
- X#endif
- X if(!(potion = getobj("!", "dip into")))
- X return(0);
- X#ifndef KAA
- X pline("Interesting...");
- X#else
- X if(potion->otyp == POT_HOLY_WATER) {
- X if (obj->cursed) {
- X obj->cursed=0;
- X pline("Your %s %s.", aobjnam(obj,"softly glow"),
- X Hallucination ? hcolor() : "amber");
- X poof: useup(potion);
- X return(1);
- X } else if(obj->otyp >= ARROW && obj->otyp <= SPEAR) {
- X obj->dknown=1;
- X tmp = Hallucination ? hcolor() : "light blue";
- X /* dknown for weapons is meaningless, so it's free to be reused. */
- X pline("Your %s with a%s %s aura.", aobjnam(obj,"softly glow"),
- X index("aeiou",*tmp) ? "n" : "", tmp);
- X goto poof;
- X }
- X }
- X#endif
- X if(obj->otyp == ARROW || obj->otyp == DART ||
- X obj->otyp == CROSSBOW_BOLT || obj->otyp == SHURIKEN) {
- X if(potion->otyp == POT_SICKNESS) {
- X char buf[BUFSZ];
- X useup(potion);
- X if(obj->spe < 7) obj->spe++; /* %% */
- X sprintf(buf, xname(potion));
- X pline("The %s forms a coating on the %s.",
- X buf, xname(obj));
- X }
- X }
- X#ifdef KAA
- X pline("Interesting...");
- X#endif
- X return(1);
- X}
- X
- Xghost_from_bottle(){
- X extern struct permonst pm_ghost;
- X register struct monst *mtmp;
- X
- X if(!(mtmp = makemon(PM_GHOST,u.ux,u.uy))){
- X pline("This bottle turns out to be empty.");
- X return;
- X }
- X mnexto(mtmp);
- X pline("As you open the bottle, an enormous ghost emerges!");
- X pline("You are frightened to death, and unable to move.");
- X nomul(-3);
- X}
- X
- Xgainstr(inc)
- Xregister int inc;
- X{
- X if(u.ustr >= 118) return; /* > 118 is impossible */
- X
- X if((u.ustr > 17) && !inc) u.ustr += rnd(118 - u.ustr);
- X#ifdef HARD
- X else u.ustr++;
- X#else
- X else u.ustr += (inc) ? 1 : rnd(3);
- X#endif
- X
- X if(u.ustr > u.ustrmax) u.ustrmax = u.ustr;
- X flags.botl = 1;
- X}
- END_OF_potion.c
- if test 13424 -ne `wc -c <potion.c`; then
- echo shar: \"potion.c\" unpacked with wrong size!
- fi
- # end of overwriting check
- fi
- if test -f unixunix.c -a "${1}" != "-c" ; then
- echo shar: Will not over-write existing file \"unixunix.c\"
- else
- echo shar: Extracting \"unixunix.c\" \(10405 characters\)
- sed "s/^X//" >unixunix.c <<'END_OF_unixunix.c'
- X/* SCCS Id: @(#)unixunix.c 1.3 87/07/14
- X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
- X/* hack.unix.c - version 1.0.3 */
- X
- X/* This file collects some Unix dependencies; pager.c contains some more */
- X
- X/*
- X * The time is used for:
- X * - seed for rand()
- X * - year on tombstone and yymmdd in record file
- X * - phase of the moon (various monsters react to NEW_MOON or FULL_MOON)
- X * - night and midnight (the undead are dangerous at midnight)
- X * - determination of what files are "very old"
- X */
- X
- X#include <stdio.h>
- X#include <errno.h>
- X#include "hack.h" /* mainly for index() which depends on BSD */
- X
- X#include <sys/types.h> /* for time_t and stat */
- X#include <sys/stat.h>
- X#ifdef BSD
- X#include <sys/time.h>
- X#else
- X#include <time.h>
- X#endif
- X
- Xextern char *getenv();
- Xextern time_t time();
- X
- Xsetrandom()
- X{
- X (void) srand((int) time ((time_t *) 0));
- X}
- X
- Xstruct tm *
- Xgetlt()
- X{
- X time_t date;
- X struct tm *localtime();
- X
- X (void) time(&date);
- X return(localtime(&date));
- X}
- X
- Xgetyear()
- X{
- X return(1900 + getlt()->tm_year);
- X}
- X
- Xchar *
- Xgetdate()
- X{
- X static char datestr[7];
- X register struct tm *lt = getlt();
- X
- X (void) sprintf(datestr, "%2d%2d%2d",
- X lt->tm_year, lt->tm_mon + 1, lt->tm_mday);
- X if(datestr[2] == ' ') datestr[2] = '0';
- X if(datestr[4] == ' ') datestr[4] = '0';
- X return(datestr);
- X}
- X
- Xphase_of_the_moon() /* 0-7, with 0: new, 4: full */
- X{ /* moon period: 29.5306 days */
- X /* year: 365.2422 days */
- X register struct tm *lt = getlt();
- X register int epact, diy, golden;
- X
- X diy = lt->tm_yday;
- X golden = (lt->tm_year % 19) + 1;
- X epact = (11 * golden + 18) % 30;
- X if ((epact == 25 && golden > 11) || epact == 24)
- X epact++;
- X
- X return( (((((diy + epact) * 6) + 11) % 177) / 22) & 7 );
- X}
- X
- Xnight()
- X{
- X register int hour = getlt()->tm_hour;
- X
- X return(hour < 6 || hour > 21);
- X}
- X
- Xmidnight()
- X{
- X return(getlt()->tm_hour == 0);
- X}
- X
- Xstruct stat buf, hbuf;
- X
- Xgethdate(name) char *name; {
- X/* old version - for people short of space */
- X/*
- X/* register char *np;
- X/* if(stat(name, &hbuf))
- X/* error("Cannot get status of %s.",
- X/* (np = rindex(name, '/')) ? np+1 : name);
- X/*
- X/* version using PATH from: seismo!gregc@ucsf-cgl.ARPA (Greg Couch) */
- X
- X
- X/*
- X * The problem with #include <sys/param.h> is that this include file
- X * does not exist on all systems, and moreover, that it sometimes includes
- X * <sys/types.h> again, so that the compiler sees these typedefs twice.
- X */
- X#define MAXPATHLEN 1024
- X
- Xregister char *np, *path;
- Xchar filename[MAXPATHLEN+1];
- X if (index(name, '/') != NULL || (path = getenv("PATH")) == NULL)
- X path = "";
- X
- X for (;;) {
- X if ((np = index(path, ':')) == NULL)
- X np = path + strlen(path); /* point to end str */
- X if (np - path <= 1) /* %% */
- X (void) strcpy(filename, name);
- X else {
- X (void) strncpy(filename, path, np - path);
- X filename[np - path] = '/';
- X (void) strcpy(filename + (np - path) + 1, name);
- X }
- X if (stat(filename, &hbuf) == 0)
- X return;
- X if (*np == '\0')
- X break;
- X path = np + 1;
- X }
- X error("Cannot get status of %s.",
- X (np = rindex(name, '/')) ? np+1 : name);
- X}
- X
- Xuptodate(fd) {
- X if(fstat(fd, &buf)) {
- X pline("Cannot get status of saved level? ");
- X return(0);
- X }
- X if(buf.st_mtime < hbuf.st_mtime) {
- X pline("Saved level is out of date. ");
- X return(0);
- X }
- X return(1);
- X}
- X
- X/* see whether we should throw away this xlock file */
- Xveryold(fd) {
- X register int i;
- X time_t date;
- X
- X if(fstat(fd, &buf)) return(0); /* cannot get status */
- X if(buf.st_size != sizeof(int)) return(0); /* not an xlock file */
- X (void) time(&date);
- X if(date - buf.st_mtime < 3L*24L*60L*60L) { /* recent */
- X extern int errno;
- X int lockedpid; /* should be the same size as hackpid */
- X
- X if(read(fd, (char *)&lockedpid, sizeof(lockedpid)) !=
- X sizeof(lockedpid))
- X /* strange ... */
- X return(0);
- X
- X /* From: Rick Adams <seismo!rick>
- X /* This will work on 4.1cbsd, 4.2bsd and system 3? & 5.
- X /* It will do nothing on V7 or 4.1bsd. */
- X if(!(kill(lockedpid, 0) == -1 && errno == ESRCH))
- X return(0);
- X }
- X (void) close(fd);
- X for(i = 1; i <= MAXLEVEL; i++) { /* try to remove all */
- X glo(i);
- X (void) unlink(lock);
- X }
- X glo(0);
- X if(unlink(lock)) return(0); /* cannot remove it */
- X return(1); /* success! */
- X}
- X
- Xgetlock()
- X{
- X extern int errno, hackpid, locknum;
- X register int i = 0, fd;
- X
- X (void) fflush(stdout);
- X
- X /* we ignore QUIT and INT at this point */
- X if (link(HLOCK, LLOCK) == -1) {
- X register int errnosv = errno;
- X
- X perror(HLOCK);
- X printf("Cannot link %s to %s\n", LLOCK, HLOCK);
- X switch(errnosv) {
- X case ENOENT:
- X printf("Perhaps there is no (empty) file %s ?\n", HLOCK);
- X break;
- X case EACCES:
- X printf("It seems you don't have write permission here.\n");
- X break;
- X case EEXIST:
- X printf("(Try again or rm %s.)\n", LLOCK);
- X break;
- X default:
- X printf("I don't know what is wrong.");
- X }
- X getret();
- X error("");
- X /*NOTREACHED*/
- X }
- X
- X regularize(lock);
- X glo(0);
- X if(locknum > 25) locknum = 25;
- X
- X do {
- X if(locknum) lock[0] = 'a' + i++;
- X
- X if((fd = open(lock, 0)) == -1) {
- X if(errno == ENOENT) goto gotlock; /* no such file */
- X perror(lock);
- X (void) unlink(LLOCK);
- X error("Cannot open %s", lock);
- X }
- X
- X if(veryold(fd)) /* if true, this closes fd and unlinks lock */
- X goto gotlock;
- X (void) close(fd);
- X } while(i < locknum);
- X
- X (void) unlink(LLOCK);
- X error(locknum ? "Too many hacks running now."
- X : "There is a game in progress under your name.");
- Xgotlock:
- X fd = creat(lock, FMASK);
- X if(unlink(LLOCK) == -1)
- X error("Cannot unlink %s.", LLOCK);
- X if(fd == -1) {
- X error("cannot creat lock file.");
- X } else {
- X if(write(fd, (char *) &hackpid, sizeof(hackpid))
- X != sizeof(hackpid)){
- X error("cannot write lock");
- X }
- X if(close(fd) == -1) {
- X error("cannot close lock");
- X }
- X }
- X}
- X
- X#ifdef MAIL
- X
- X/*
- X * Notify user when new mail has arrived. [Idea from Merlyn Leroy, but
- X * I don't know the details of his implementation.]
- X * { Later note: he disliked my calling a general mailreader and felt that
- X * hack should do the paging itself. But when I get mail, I want to put it
- X * in some folder, reply, etc. - it would be unreasonable to put all these
- X * functions in hack. }
- X * The mail daemon '2' is at present not a real monster, but only a visual
- X * effect. Thus, makemon() is superfluous. This might become otherwise,
- X * however. The motion of '2' is less restrained than usual: diagonal moves
- X * from a DOOR are possible. He might also use SDOOR's. Also, '2' is visible
- X * in a ROOM, even when you are Blind.
- X * Its path should be longer when you are Telepat-hic and Blind.
- X *
- X * Interesting side effects:
- X * - You can get rich by sending yourself a lot of mail and selling
- X * it to the shopkeeper. Unfortunately mail isn't very valuable.
- X * - You might die in case '2' comes along at a critical moment during
- X * a fight and delivers a scroll the weight of which causes you to
- X * collapse.
- X *
- X * Possible extensions:
- X * - Open the file MAIL and do fstat instead of stat for efficiency.
- X * (But sh uses stat, so this cannot be too bad.)
- X * - Examine the mail and produce a scroll of mail called "From somebody".
- X * - Invoke MAILREADER in such a way that only this single letter is read.
- X *
- X * - Make him lose his mail when a Nymph steals the letter.
- X * - Do something to the text when the scroll is enchanted or cancelled.
- X */
- X#include "mkroom.h"
- Xstatic struct stat omstat,nmstat;
- Xstatic char *mailbox;
- Xstatic long laststattime;
- X
- Xgetmailstatus() {
- X if(!(mailbox = getenv("MAIL")))
- X return;
- X if(stat(mailbox, &omstat)){
- X#ifdef PERMANENT_MAILBOX
- X pline("Cannot get status of MAIL=%s .", mailbox);
- X mailbox = 0;
- X#else
- X omstat.st_mtime = 0;
- X#endif
- X }
- X}
- X
- Xckmailstatus() {
- X if(!mailbox
- X#ifdef MAILCKFREQ
- X || moves < laststattime + MAILCKFREQ
- X#endif
- X )
- X return;
- X laststattime = moves;
- X if(stat(mailbox, &nmstat)){
- X#ifdef PERMANENT_MAILBOX
- X pline("Cannot get status of MAIL=%s anymore.", mailbox);
- X mailbox = 0;
- X#else
- X nmstat.st_mtime = 0;
- X#endif
- X } else if(nmstat.st_mtime > omstat.st_mtime) {
- X if(nmstat.st_size)
- X newmail();
- X getmailstatus(); /* might be too late ... */
- X }
- X}
- X
- Xnewmail() {
- X /* produce a scroll of mail */
- X register struct obj *obj;
- X register struct monst *md;
- X extern char plname[];
- X extern struct obj *mksobj(), *addinv();
- X extern struct monst *makemon();
- X extern struct permonst pm_mail_daemon;
- X
- X obj = mksobj(SCR_MAIL);
- X if(md = makemon(&pm_mail_daemon, u.ux, u.uy)) /* always succeeds */
- X mdrush(md,0);
- X
- X pline("\"Hello, %s! I have some mail for you.\"", plname);
- X if(md) {
- X if(dist(md->mx,md->my) > 2)
- X pline("\"Catch!\"");
- X more();
- X
- X /* let him disappear again */
- X mdrush(md,1);
- X mondead(md);
- X }
- X
- X obj = addinv(obj);
- X (void) identify(obj); /* set known and do prinv() */
- X}
- X
- X/* make md run through the cave */
- Xmdrush(md,away)
- Xregister struct monst *md;
- Xboolean away;
- X{
- X register int uroom = inroom(u.ux, u.uy);
- X if(uroom >= 0) {
- X register int tmp = rooms[uroom].fdoor;
- X register int cnt = rooms[uroom].doorct;
- X register int fx = u.ux, fy = u.uy;
- X while(cnt--) {
- X if(dist(fx,fy) < dist(doors[tmp].x, doors[tmp].y)){
- X fx = doors[tmp].x;
- X fy = doors[tmp].y;
- X }
- X tmp++;
- X }
- X tmp_at(-1, md->data->mlet); /* open call */
- X if(away) { /* interchange origin and destination */
- X unpmon(md);
- X tmp = fx; fx = md->mx; md->mx = tmp;
- X tmp = fy; fy = md->my; md->my = tmp;
- X }
- X while(fx != md->mx || fy != md->my) {
- X register int dx,dy,nfx = fx,nfy = fy,d1,d2;
- X
- X tmp_at(fx,fy);
- X d1 = DIST(fx,fy,md->mx,md->my);
- X for(dx = -1; dx <= 1; dx++) for(dy = -1; dy <= 1; dy++)
- X if(dx || dy) {
- X d2 = DIST(fx+dx,fy+dy,md->mx,md->my);
- X if(d2 < d1) {
- X d1 = d2;
- X nfx = fx+dx;
- X nfy = fy+dy;
- X }
- X }
- X if(nfx != fx || nfy != fy) {
- X fx = nfx;
- X fy = nfy;
- X } else {
- X if(!away) {
- X md->mx = fx;
- X md->my = fy;
- X }
- X break;
- X }
- X }
- X tmp_at(-1,-1); /* close call */
- X }
- X if(!away)
- X pmon(md);
- X}
- X
- Xreadmail() {
- X#ifdef DEF_MAILREADER /* This implies that UNIX is defined */
- X register char *mr = 0;
- X more();
- X if(!(mr = getenv("MAILREADER")))
- X mr = DEF_MAILREADER;
- X if(child(1)){
- X execl(mr, mr, (char *) 0);
- X exit(1);
- X }
- X#else
- X (void) page_file(mailbox, FALSE);
- X#endif
- X /* get new stat; not entirely correct: there is a small time
- X window where we do not see new mail */
- X getmailstatus();
- X}
- X#endif /* MAIL /**/
- X
- Xregularize(s) /* normalize file name - we don't like ..'s or /'s */
- Xregister char *s;
- X{
- X register char *lp;
- X
- X while((lp = index(s, '.')) || (lp = index(s, '/')))
- X *lp = '_';
- X}
- END_OF_unixunix.c
- if test 10405 -ne `wc -c <unixunix.c`; then
- echo shar: \"unixunix.c\" unpacked with wrong size!
- fi
- # end of overwriting check
- fi
- echo shar: End of archive 7 \(of 16\).
- cp /dev/null ark7isdone
- MISSING=""
- for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 ; do
- if test ! -f ark${I}isdone ; then
- MISSING="${MISSING} ${I}"
- fi
- done
- if test "${MISSING}" = "" ; then
- echo You have unpacked all 16 archives.
- rm -f ark[1-9]isdone ark[1-9][0-9]isdone
- else
- echo You still need to unpack the following archives:
- echo " " ${MISSING}
- fi
- ## End of shell archive.
- exit 0
-